<!DOCTYPE html>
<html lang="zh-cn">

<head>
  <meta charset="UTF-8" />
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
  <title>快捷任务</title>
  <style>
    * {
      margin: 0;
      padding: 0;
    }

    div {
      box-sizing: border-box;
    }

    body {
      font-family: Menlo, Monaco, 'Courier New', ui-monospace;
    }

    .con {
      width: 100%;
      height: 100%;
      padding: 20px;
    }

    .card {
      width: 100%;
      border: 1px solid #ebeef5;
      border-radius: 10px;
      box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
      margin: 10px 0;
      /* padding: 10px 20px; */
    }

    .card:first-child {
      margin: 0;
    }

    .card-header {
      font-size: 20px;
      line-height: 40px;
      padding: 15px 20px;
      border-bottom: 1px solid #ebeef5;
      display: flex;
      flex-direction: column;
    }

    .card-header-title {
      display: flex;
      justify-content: space-between;
      align-items: center;
    }

    .card-header-input {
      display: flex;
    }

    .card-body {
      padding: 15px;
    }

    .card-body-date {
      margin-right: 10px;
    }

    .card-body-cons {
      display: flex;
      align-items: center;
    }

    .card-body-buttons {
      display: flex;
      align-items: center;
    }

    .card-body-line {
      display: flex;
      justify-content: space-between;
      height: 40px;
      border-radius: 3px;
      padding: 0 10px;
    }

    .card-body-line:hover {
      background-color: #f5f5f5;
    }

    .card-body-line:hover button {
      background-color: #f5f5f5;
    }

    .card-body-button {
      margin-left: 10px;
      cursor: pointer;
    }

    .check {
      /* margin-left: 20px; */
      display: inline-block;
      width: 8px;
      height: 16px;
      border-color: #009933;
      border-style: solid;
      border-width: 0 5px 5px 0;
      transform: rotate(45deg);
      visibility: hidden;
    }

    input {
      background-color: #fff;
      background-image: none;
      border-radius: 4px;
      border: 1px solid #bdbfc2;
      box-sizing: border-box;
      color: #606266;
      display: inline-block;
      height: 35px;
      line-height: 35px;
      outline: none;
      margin-right: 10px;
      padding: 0 15px;
      transition: border-color 0.2s cubic-bezier(0.645, 0.045, 0.355, 1);
    }

    input::placeholder {
      color: #cbcccf;
      font-size: 14px;
    }

    input:focus {
      outline: none;
      border-color: #409eff;
    }

    button {
      display: inline-block;
      line-height: 1;
      white-space: nowrap;
      cursor: pointer;
      background: #fff;
      border: 1px solid #bdbfc2;
      color: #606266;
      text-align: center;
      box-sizing: border-box;
      outline: none;
      margin: 0;
      transition: 0.1s;
      font-weight: 500;
      padding: 0 20px;
      height: 35px;
      font-size: 14px;
      border-radius: 4px;
    }

    button:hover {
      color: #409eff;
      border-color: #c6e2ff;
      background-color: #ecf5ff;
    }

    button:active {
      color: #3a8ee6;
      border-color: #3a8ee6;
      outline: none;
    }

    .hidden {
      display: none;
    }

    .add-card-input {
      width: 130px;
      margin-right: 5px;
    }

    .con .card {
      margin-bottom: 10px;
    }

    .con-input {
      width: 700px;
    }

    .moving {
      background: transparent;
      color: transparent;
      border: 1px dashed #ccc;
    }
  </style>
</head>

<body>
  <div class="con">
    <div class="card">
      <div class="card-header hidden"></div>
      <div class="card-body">
        <input type="number" id="addmonth" class="add-card-input" placeholder="请输入月份" />
        <button onclick="addCard()">添加卡片</button>
        <button onclick="showDelCard(this)">删除卡片</button>
        <button onclick="showDelData(this)">删除卡片中数据</button>
      </div>
    </div>

    <div id="fcard"></div>
  </div>

  <script>
    //创建元素 insertFlag '1' 正序 '2' 插入到列表第一个
    function creatDiv(domStr, fDom, fDomClassName, insertFlag, isdraggable) {
      let newDiv = document.createElement("div");
      newDiv.innerHTML = domStr;
      newDiv.classList.add(fDomClassName);
      if (isdraggable) {
        newDiv.setAttribute("draggable", "true");
      }
      if (insertFlag === '1') {
        fDom.appendChild(newDiv);
      } else if (insertFlag === '2') {
        fDom.insertBefore(newDiv, fDom.firstChild);
      }
    }
    //网页复制api
    async function writeDataToClipboard(text) {
      try {
        await navigator.clipboard.writeText(text);
      } catch (error) {
        alert("复制失败");
      }
    }
    //获取所有数据
    function getAllArr() {
      let allArr = localStorage.getItem("allArr");
      allArr = allArr ? JSON.parse(allArr) : allArr;
      return allArr;
    }

    //设置所有数据
    function setAllArr(array) {
      localStorage.setItem("allArr", JSON.stringify(array));
    }

    //获取月份数据
    function getMonthArr(month) {
      let key = "arr" + month;
      let allArr = getAllArr();
      let monthArr = allArr.find((item) => item.key === key);
      return monthArr ? monthArr.value : monthArr;
    }
    //设置月份数据
    function setMonthArr(array, month) {
      let key = "arr" + month;
      let value = array;

      let allArr = getAllArr();
      let monthArr = allArr.find((item) => item.key === key);
      if (monthArr) {
        let index = allArr.findIndex((item) => item.key === key);
        allArr[index].value = array;
      } else {
        allArr.unshift({ key, value });
      }
      setAllArr(allArr);
    }

    //按钮方法
    function copyAndopen(dom, num) {
      let fdom = dom.parentElement.parentElement;
      let serialNumberStr = fdom.firstElementChild.children[1].innerHTML;
      let textStr = fdom.firstElementChild.children[2].innerHTML;
      let allStr = serialNumberStr + textStr;
      switch (num) {
        case 1:
          //复制序号
          writeDataToClipboard(serialNumberStr);
          break;
        case 2:
          //复制整体
          writeDataToClipboard(allStr);
          break;
        case 3:
          //打开git
          let url = "error";
          if (serialNumberStr.slice(0, 8) === "PCICXKS2") {
            url = `http://gitlab.djbx.com/DJ-CX/PCICXKS2/dajia-front_v1/-/commits/${serialNumberStr}?ref_type=heads`;
          } else if (serialNumberStr.slice(0, 8) === "PCIYWZTS") {
            if (textStr.includes('车智')) {
              url = `http://gitlab.djbx.com/DJ-CX/CXHX/cxhxintelligentplatfront/-/commits/${serialNumberStr}?ref_type=heads`;
            } else {
              url = `http://gitlab.djbx.com/DJ-CX/CXHX/cxhxmunualunderwrite/-/commits/${serialNumberStr}?ref_type=heads`;
            }
          }
          window.open(url, "_blank");
          break;
        case 4:
          //打开erm
          window.open(
            `http://erm.djbx.com/browse/${serialNumberStr}`,
            "_blank"
          );
          break;
      }
    }

    //添加具体数据
    function addLineDom(info, fDom, insertFlag) {
      let domStr = `
          <div class="card-body-cons" draggable="false">
              <div class="card-body-date" draggable="false">${info.date}</div>
              <div class="card-body-num" draggable="false">${info.num}</div>
              <div class="card-body-con" draggable="false">${info.text}</div>
          </div>
          <div class="card-body-buttons" draggable="false">
              <button class="card-body-button" onclick="copyAndopen(this, 1)">复制序号</button>
              <button class="card-body-button" onclick="copyAndopen(this, 2)">复制整体</button>
              <button class="card-body-button" onclick="copyAndopen(this, 3)">打开git</button>
              <button class="card-body-button" onclick="copyAndopen(this, 4)">打开erm</button>
              <button class="card-body-button hidden show" onclick="delData(this)">删除数据</button>
              <button class="card-body-button show" onclick="editData(this)">修改数据</button>
          </div>
          `;
      creatDiv(domStr, fDom, "card-body-line", insertFlag, true);
    }

    //添加具体数据
    function addCardDom(month, fDom, insertFlag) {
      let domStr = `
          <div class="card-header">
            <div class="card-header-title">
              <div>${month}月</div>
              <div>
                <button onclick="showAddData(this)">添加数据</button>
                <button onclick="delCard(this)" class="hidden show-del-card">删除卡片</button>
              </div>
            </div>
            <div class="card-header-input hidden">
              <input type="number" name="day" class="date-input" placeholder="请输入上线日期" />
              <input type="text" name="num" class="num-input" placeholder="请输入序号" />
              <input type="text" name="text" class="con-input" placeholder="请输入文字" />
              <button onclick="addDataSure(this)">确定</button>
            </div>
          </div>
          <div class="card-body" id="card${month}"></div>
          `;
      creatDiv(domStr, fDom, "card", insertFlag);
    }

    function addDataSure(dom) {
      //获取页面上3个输入框里的值
      let domList = dom.parentElement.children;
      let date = domList[0].value;
      let num = domList[1].value;
      let text = domList[2].value;
      if (date === "" || num === "" || text === "") {
        alert("请输入完整信息");
        return;
      }
      let monthDom =
        dom.parentElement.parentElement.firstElementChild.firstElementChild;
      let month = monthDom.innerText.split("月")[0];
      //对象字面量的简写语法
      let info = { date, num, text };
      //存储数据
      let arr = getMonthArr(month);
      arr.unshift(info);
      setMonthArr(arr, month);
      //添加dom
      let fDom =
        dom.parentElement.parentElement.parentElement.lastElementChild;
      addLineDom(info, fDom, "2");
      domList[0].value = "";
      domList[1].value = "";
      domList[2].value = "";
    }

    function editData(element) {
      let itemdom = element.parentElement.parentElement;
      let fdom = element.parentElement.parentElement.parentNode;
      let children = fdom.children;
      let monthDom =
        element.parentElement.parentElement.parentElement.parentElement
          .firstElementChild.firstElementChild.firstElementChild;
      let month = monthDom.innerText.split("月")[0];
      let index = Array.from(children).indexOf(itemdom);
      let arr = getMonthArr(month);
      let item = arr[index];
      let str = prompt('请输入修改后信息');
      if (str) {
        let resArr = str.replace(/[,，;；。、.]/g, '/').split('/');
        let day = resArr[0];
        let number = resArr[1];
        if (day) {
          item.date = day;
        }
        if (number) {
          item.num = number;
        }
        setMonthArr(arr, month);
        location.reload();
      };
    }

    //显示添加数据输入框
    function showAddData(dom) {
      let inputDom =
        dom.parentElement.parentElement.parentElement.lastElementChild;
      // 获取元素的计算样式
      let computedStyle = window.getComputedStyle(inputDom);

      // 获取元素的 display 属性
      let displayPropertyValue = computedStyle.getPropertyValue("display");
      if (displayPropertyValue === "flex") {
        inputDom.classList.add("hidden");
        dom.innerHTML = "添加数据";
      } else {
        inputDom.classList.remove("hidden");
        dom.innerHTML = "添加完成";
      }
    }

    //显示删除数据按钮
    function showDelData(dom) {
      let styleList = document.querySelectorAll("style");
      let styleListLength = styleList.length;

      if (styleListLength === 1) {
        dom.innerHTML = "删除完成";
        // 创建一个style元素
        let styleElement = document.createElement("style");
        // 设置style元素的内容（CSS规则）
        styleElement.textContent = `.show { display: inline-block; }`;
        // 将style元素添加到<head>标签内
        document.head.appendChild(styleElement);
      } else {
        // 创建一个style元素
        let styleElement = document.createElement("style");
        // 设置style元素的内容（CSS规则）
        styleElement.textContent = `.show { display: inline-block; }`;
        // 将style元素添加到<head>标签内
        document.head.appendChild(styleElement);

        let styleList = document.querySelectorAll("style");
        let styleListLength = styleList.length;
        let lastStyle = styleList[styleListLength - 1];

        let equalNodeIndex = [];
        //遍历所有style元素
        for (let i = 0; i < styleListLength; i++) {
          if (styleList[i].isEqualNode(lastStyle)) {
            equalNodeIndex.push(i);
          }
        }
        dom.innerHTML = "删除完成";
        if (equalNodeIndex.length === 2) {
          equalNodeIndex.forEach((item) => {
            styleList[item].remove();
          });
          dom.innerHTML = "删除卡片中数据";
        }
      }
    }

    //显示删除卡片按钮
    function showDelCard(dom) {
      let styleList = document.querySelectorAll("style");
      let styleListLength = styleList.length;

      if (styleListLength === 1) {
        dom.innerHTML = "删除完成";
        // 创建一个style元素
        let styleElement = document.createElement("style");
        // 设置style元素的内容（CSS规则）
        styleElement.textContent = `.show-del-card { display: inline-block; }`;
        // 将style元素添加到<head>标签内
        document.head.appendChild(styleElement);
      } else {
        // 创建一个style元素
        let styleElement = document.createElement("style");
        // 设置style元素的内容（CSS规则）
        styleElement.textContent = `.show-del-card { display: inline-block; }`;
        // 将style元素添加到<head>标签内
        document.head.appendChild(styleElement);

        let styleList = document.querySelectorAll("style");
        let styleListLength = styleList.length;
        let lastStyle = styleList[styleListLength - 1];

        let equalNodeIndex = [];
        //遍历所有style元素
        for (let i = 0; i < styleListLength; i++) {
          if (styleList[i].isEqualNode(lastStyle)) {
            equalNodeIndex.push(i);
          }
        }
        dom.innerHTML = "删除完成";
        if (equalNodeIndex.length === 2) {
          equalNodeIndex.forEach((item) => {
            styleList[item].remove();
          });
          dom.innerHTML = "删除卡片";
        }
      }
    }

    //删除数据
    function delData(element) {
      let itemdom = element.parentElement.parentElement;
      let fdom = element.parentElement.parentElement.parentNode;
      let children = fdom.children;
      let monthDom =
        element.parentElement.parentElement.parentElement.parentElement
          .firstElementChild.firstElementChild.firstElementChild;
      let month = monthDom.innerText.split("月")[0];
      let index = Array.from(children).indexOf(itemdom);
      let arr = getMonthArr(month);
      arr.splice(index, 1);
      setMonthArr(arr, month);
      itemdom.remove();
    }
    //添加卡片
    function addCard() {
      let month = document.getElementById("addmonth").value;
      if (!month) return alert("请输入月份");
      if (month < 1 || month > 12) return alert("请输入1到12之间的月份");
      if (getMonthArr(month)) return alert("该月份已经存在");

      let fDom = document.getElementById("fcard");
      addCardDom(month, fDom, "2");
      setMonthArr([], month);
      document.getElementById("addmonth").value = "";
    }
    //删除卡片
    function delCard(dom) {
      const confirmDelete = window.confirm("确定要删除吗？");
      if (!confirmDelete) return;
      let itemdom = dom.parentElement.parentElement.parentElement.parentElement;
      let fdom = dom.parentElement.parentElement.parentElement.parentElement.parentNode;
      let children = fdom.children;
      let index = Array.from(children).indexOf(itemdom);
      let arr = getAllArr();
      arr.splice(index, 1);
      setAllArr(arr);
      itemdom.remove();
    }

    //交换数组中两个元素的位置
    function swap(arr, i, j) {
      let temp = arr[i];
      arr[i] = arr[j];
      arr[j] = temp;
    }

    //添加交换功能
    function addSwap(month) {
      const sortableList = document.querySelector(`#card${month}`);
      if (!sortableList) return;
      const items = sortableList.childNodes;
      let startIndex, endIndex;

      items.forEach((item) => {
        //拖动开始
        item.addEventListener("dragstart", (e) => {
          setTimeout(() => {
            item.classList.add("moving");
          }, 0);
          startIndex = Array.from(items).indexOf(e.target);
        });
        //拖动结束
        item.addEventListener("dragend", (e) => {
          item.classList.remove("moving");
          endIndex = Array.from(items).indexOf(e.target);

          let step = endIndex - startIndex;
          let resArr = getMonthArr(month);

          if (step > 0) {
            for (let i = startIndex; i < startIndex + step; i++) {
              swap(resArr, i, i + 1);
            }
          } else if (step < 0) {
            for (let i = startIndex; i >= startIndex + step + 1; i--) {
              swap(resArr, i, i - 1);
            }
          } else {
            return;
          }
          setMonthArr(resArr, month);
        });
      });

      const initSortableList = (e) => {
        e.preventDefault();
        const draggingItem = sortableList.querySelector(".moving");
        const siblings = [
          ...sortableList.querySelectorAll(".card-body-line:not(.moving)"),
        ];
        let nextSibling = siblings.find((sibling) => {
          return e.clientY <= sibling.offsetTop + sibling.offsetHeight / 2;
        });
        sortableList.insertBefore(draggingItem, nextSibling);
      };
      sortableList.addEventListener("dragover", initSortableList);
      sortableList.addEventListener("dragenter", (e) => e.preventDefault());
    }

    //进入页面时，加载数据
    function loadData() {
      let allArray = getAllArr();
      if (!allArray) return setAllArr([]);
      //页面初始化数据
      let allCardData = allArray;

      //创建卡片dom
      let fDom = document.getElementById("fcard");
      allCardData.forEach((item) => {
        let month = item.key.split("arr")[1];
        addCardDom(month, fDom, "1");
        //创建卡牌中数据dom
        let targetDom = document.getElementById(`card${month}`);
        let arr = getMonthArr(month);
        arr.forEach((item) => {
          addLineDom(item, targetDom, "1");
        });
      });
    }
    loadData();

    window.addEventListener("load", function () {
      // 在所有资源加载完成后执行JavaScript代码
      //获取所有卡片
      let allCardData = getAllArr();
      allCardData.forEach((item) => {
        let month = item.key.split("arr")[1];
        addSwap(month);
      });
    });
  </script>
</body>

</html>